#pragma once

#include <atomic>

#include <IMG/IMG.h>
#include <ShObjIdl.h>

struct IMGShellExtShellView final : public IShellFolder, public IPersistFolder
{
    IMGShellExtShellView( IMG& imgHandle );
    ~IMGShellExtShellView( void );

    // IUnknown.
    IFACEMETHODIMP QueryInterface( REFIID riid, void **ppv ) override;
    IFACEMETHODIMP_(ULONG) AddRef( void ) override;
    IFACEMETHODIMP_(ULONG) Release( void ) override;

    // IShellFolder
    IFACEMETHODIMP BindToObject( PCUIDLIST_RELATIVE idlist, IBindCtx *bindCtx, REFIID riid, void **ppv ) override;
    IFACEMETHODIMP BindToStorage( PCUIDLIST_RELATIVE idlist, IBindCtx *bindCtx, REFIID riid, void **ppv ) override;

    IFACEMETHODIMP CompareIDs( LPARAM lParam, PCUIDLIST_RELATIVE idfirst, PCUIDLIST_RELATIVE idsecond ) override;

    IFACEMETHODIMP CreateViewObject( HWND wndObj, REFIID riid, void **ppv ) override;

    IFACEMETHODIMP EnumObjects( HWND wndObj, SHCONTF grfFlags, IEnumIDList **ppenum ) override;
    IFACEMETHODIMP GetAttributesOf( UINT cidl, PCUITEMID_CHILD_ARRAY apidl, SFGAOF *rgfInOut ) override;
    IFACEMETHODIMP GetDisplayNameOf( PCUITEMID_CHILD idl, SHGDNF uFlags, STRRET *pName ) override;

    IFACEMETHODIMP GetUIObjectOf( HWND wndObj, UINT cidl, PCUITEMID_CHILD_ARRAY apidl, REFIID riid, UINT *rgfReserved, void **ppv ) override;

    IFACEMETHODIMP ParseDisplayName( HWND wndObj, IBindCtx *bindCtx, LPWSTR dispName, ULONG *pchEaten, PIDLIST_RELATIVE *ppidl, ULONG *pdwAttrib ) override;
    IFACEMETHODIMP SetNameOf( HWND wndObj, PCUITEMID_CHILD pidl, LPCWSTR pszName, SHGDNF uFlags, PITEMID_CHILD *ppidlOut ) override;

    // IPersistFolder
    IFACEMETHODIMP GetClassID( CLSID *clsid ) override;
    IFACEMETHODIMP Initialize( LPCITEMIDLIST pidl ) override;

private:
    IMG imgHandle;

    std::atomic <unsigned long> refCount;
};